#!/usr/bin/env node
const crypto = require('crypto');
let bcrypt;

function usage() {
  console.log('用法: node scripts/genPassword.js [length] [--hash]');
  console.log('示例: node scripts/genPassword.js 16');
  console.log('示例(同时输出bcrypt哈希): node scripts/genPassword.js 20 --hash');
}

function pick(set) {
  const idx = crypto.randomInt(0, set.length);
  return set[idx];
}

function shuffle(arr) {
  for (let i = arr.length - 1; i > 0; i--) {
    const j = crypto.randomInt(0, i + 1);
    [arr[i], arr[j]] = [arr[j], arr[i]];
  }
  return arr;
}

function generatePassword(length = 8) {
  const lower = 'abcdefghijklmnopqrstuvwxyz';
  const upper = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ';
  const digits = '0123456789';
  const symbols = '!@#$%^&*()-_=+[]{};:,.<>/?';

  const all = lower + upper + digits + symbols;
  const required = [pick(lower), pick(upper), pick(digits), pick(symbols)];

  const result = [...required];
  while (result.length < length) {
    result.push(pick(all));
  }

  return shuffle(result).join('');
}

async function main() {
  const args = process.argv.slice(2);
  const wantsHash = args.includes('--hash');
  const lenArg = args.find(a => /^(\d+)$/.test(a));
  const length = lenArg ? parseInt(lenArg, 10) : 16;

  if (args.includes('--help')) return usage();
  if (length < 8 || length > 128) {
    console.error('长度需在 8 到 128 之间');
    process.exit(1);
  }

  const password = generatePassword(length);
  console.log(password);

  if (wantsHash) {
    try {
      bcrypt = require('bcrypt');
      const hash = await bcrypt.hash(password, 10);
      console.log(hash);
    } catch (e) {
      console.error('生成哈希失败，请确认已安装 bcrypt:', e.message || e);
      process.exit(2);
    }
  }
}

main();